﻿using System.Collections.Generic;
using System.Diagnostics.Contracts;

namespace System.Reactive.Linq
{
	public static partial class Observable
	{
		public static TSource Last<TSource>(this IObservable<TSource> source)
		{
			Contract.Requires(source != null, null, "source != null");
			return default(TSource);
		}

		public static TSource Last<TSource>(this IObservable<TSource> source, Func<TSource, bool> predicate)
		{
			Contract.Requires(source != null, null, "source != null");
			Contract.Requires(predicate != null, null, "predicate != null");
			return default(TSource);
		}

		public static IObservable<TSource> LastAsync<TSource>(this IObservable<TSource> source)
		{
			Contract.Requires(source != null, null, "source != null");
			Contract.Ensures(Contract.Result<IObservable<TSource>>() != null, null, "Contract.Result<IObservable<TSource>>() != null");
			return null;
		}

		public static IObservable<TSource> LastAsync<TSource>(this IObservable<TSource> source, Func<TSource, bool> predicate)
		{
			Contract.Requires(source != null, null, "source != null");
			Contract.Requires(predicate != null, null, "predicate != null");
			Contract.Ensures(Contract.Result<IObservable<TSource>>() != null, null, "Contract.Result<IObservable<TSource>>() != null");
			return null;
		}

		public static TSource LastOrDefault<TSource>(this IObservable<TSource> source)
		{
			Contract.Requires(source != null, null, "source != null");
			return default(TSource);
		}

		public static TSource LastOrDefault<TSource>(this IObservable<TSource> source, Func<TSource, bool> predicate)
		{
			Contract.Requires(source != null, null, "source != null");
			Contract.Requires(predicate != null, null, "predicate != null");
			return default(TSource);
		}

		public static IObservable<TSource> LastOrDefaultAsync<TSource>(this IObservable<TSource> source)
		{
			Contract.Requires(source != null, null, "source != null");
			Contract.Ensures(Contract.Result<IObservable<TSource>>() != null, null, "Contract.Result<IObservable<TSource>>() != null");
			return null;
		}

		public static IObservable<TSource> LastOrDefaultAsync<TSource>(this IObservable<TSource> source, Func<TSource, bool> predicate)
		{
			Contract.Requires(source != null, null, "source != null");
			Contract.Requires(predicate != null, null, "predicate != null");
			Contract.Ensures(Contract.Result<IObservable<TSource>>() != null, null, "Contract.Result<IObservable<TSource>>() != null");
			return null;
		}

		public static IEnumerable<TSource> Latest<TSource>(this IObservable<TSource> source)
		{
			Contract.Requires(source != null, null, "source != null");
			Contract.Ensures(Contract.Result<IEnumerable<TSource>>() != null, null, "Contract.Result<IEnumerable<TSource>>() != null");
			return null;
		}

		public static IObservable<TResult> Let<TSource, TResult>(this IObservable<TSource> source, Func<IObservable<TSource>, IObservable<TResult>> function)
		{
			Contract.Requires(source != null, null, "source != null");
			Contract.Requires(function != null, null, "function != null");
			Contract.Ensures(Contract.Result<IObservable<TResult>>() != null, null, "Contract.Result<IObservable<TResult>>() != null");
			return null;
		}

		public static IObservable<long> LongCount<TSource>(this IObservable<TSource> source)
		{
			Contract.Requires(source != null, null, "source != null");
			Contract.Ensures(Contract.Result<IObservable<long>>() != null, null, "Contract.Result<IObservable<long>>() != null");
			return null;
		}
	}
}